//
//  VCBase.swift
//  AirlineReservation
//
//  Created by Kevin on 2019/12/27.
//  Copyright © 2019 Kevin. All rights reserved.
//

import UIKit
import LocalAuthentication

class VCBase: UIViewController {
    
    // 状态栏
    private lazy var statusHeight = UIApplication.shared.statusBarFrame.size.height
    // 导航栏
    private lazy var naviHeight = navigationController?.navigationBar.bounds.size.height ?? 0
    // 状态栏 + 导航栏
    public lazy var realHeight = statusHeight + naviHeight
    // 没搜到数据
    public lazy var noDataView:NoDataView = {
        let ui = NoDataView()
        ui.frame = CGRect(x: 0, y: SCREEN_HEIGHT * 0.5, width: SCREEN_WIDTH, height: MARGIN)
        return ui
    }()
    
    override func viewDidLoad() {
        super.viewDidLoad()
        // 隐藏返回文字
        hideBackText()
        // 背景颜色
        view.backgroundColor = COLOR_LIGHT_WHITE
    }
    
    override func viewWillAppear(_ animated: Bool) {
        navigationController?.navigationBar.setBackgroundImage(UIImage(), for: .default)
        navigationController?.navigationBar.shadowImage = UIImage()
    }
    
    // MARK: 隐藏返回文字
    private func hideBackText() -> Void {
        navigationItem.backBarButtonItem = UIBarButtonItem(title: "", style: .done, target: nil, action: nil)
        navigationController?.navigationBar.barStyle = .default
        setNeedsStatusBarAppearanceUpdate()
    }
    
    // MARK: 跳转界面隐藏TabBar，返回显示TabBar
    func pushNextVcHideShowBottomBar(vc:UIViewController) -> Void {
        hidesBottomBarWhenPushed = true
        navigationController?.pushViewController(vc, animated: true)
        hidesBottomBarWhenPushed = false
    }
    
    // MARK: 跳转、返回界面都隐藏TabBar
    func pushNextVcHideBottomBar(vc:UIViewController) -> Void {
        hidesBottomBarWhenPushed = true
        navigationController?.pushViewController(vc, animated: true)
    }
    
    // MARK: TabBar高度
    func getTabBarHeight() -> CGFloat {
        guard let height = tabBarController?.tabBar.frame.height else {
            return 0
        }
        return height
    }
    
    // MARK: 头部白色背景
    public lazy var backroundWhite: UIView = {
        let view = UIView(frame: CGRect(x: 0, y: 0, width: SCREEN_WIDTH, height: realHeight))
        view.backgroundColor = UIColor.white
        return view
    }()
    
    // MARK: 背景图片
    public lazy var backgroundImg:UIImageView = {
        let img = UIImageView(image: UIImage(named: "background_journey"))
        img.frame = CGRect(x: 0, y: MARGIN, width: SCREEN_WIDTH, height: SCREEN_HEIGHT * 0.3)
        return img
    }()
    
    override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
        view.endEditing(true)
    }
    
    // MARK: 是否不含有字母
    func isNotChar(str:String) -> Bool {
        for char in str.utf8  {
            if (char > 64 && char < 91) || (char > 96 && char < 123) {
                return false
            }
        }
        return true
    }
    
    // MARK: 跳转界面
    func pushVc(title:String,vc:UIViewController) -> Void{
        vc.title = title
        pushNextVcHideShowBottomBar(vc: vc)
    }
    
    func pushVcHideBottomBar(title:String,vc:UIViewController) -> Void{
        vc.title = title
        pushNextVcHideBottomBar(vc: vc)
    }
    
    // MARK: 圆加号
    public lazy var cirleAddView: CirleAddView = {
        let ui = CirleAddView()
        let uiX = SCREEN_WIDTH - MARGIN100
        let uiY = SCREEN_HEIGHT - MARGIN100
        ui.frame = CGRect(x: uiX, y: uiY, width: MARGIN100, height: MARGIN100)
        return ui
    }()
    
    // MARK: 指纹/人脸认证
    func process(callback:@escaping (_ status: Bool,_ biometricType:Int) -> Void) -> Void {
        let ctx = LAContext()
        let error:NSErrorPointer = nil
        let isOK = ctx.canEvaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, error: error)
        if error != nil {
            callback(false,0)
            return
        }
        if !isOK {
            callback(false,0)
            return
        }
        var biometric = 1
        var reason = "请验证系统内录入的指纹"
        if ctx.biometryType == .faceID {
            biometric = 2
            reason = "请验证系统内录入的人脸"
        }
        ctx.evaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, localizedReason: reason) { (isOK, error) in
            DispatchQueue.main.async {
                callback(isOK,biometric)
            }
        }
    }
    
    // 网络请求
    func doPost(api:String,dict:Any,isLoading:Bool = true,callback:@escaping (_ dict:NSDictionary) -> Void) -> Void {
        guard let body = try? JSONSerialization.data(withJSONObject: dict, options: .fragmentsAllowed) else {
            return
        }
        var address = UserDefaults.standard.string(forKey: SP_IP)
        if address == nil || address?.count == 0 {
            address = SP_INNTER
        }
        let realUrl = address! + api
        print("请求接口：\(realUrl),请求数据：\(dict)")
        guard let url = URL(string: realUrl) else {
            return
        }
        // 请求体
        var request = URLRequest(url: url, cachePolicy: .reloadIgnoringCacheData, timeoutInterval: 5.0)
        request.httpBody = body
        request.httpMethod = "POST"
        request.addValue("application/json", forHTTPHeaderField: "Content-Type")
        // 加载框
        if isLoading {
            showLoading(text: nil, isSupportClick: false)
        }
        // 异步请求数据
        DispatchQueue.global().async {
            let task = URLSession.shared.dataTask(with: request, completionHandler: { (data, response, error) in
                // 隐藏加载框
                self.hideHUD()
                // 请求是否出错
                if error != nil {
                    self.show(text: "请检查网络连接")
                    return
                }
                // 转JSON
                guard let dict = try? (JSONSerialization.jsonObject(with: data!, options: .mutableLeaves) as! NSDictionary ) else {
                    self.show(text: "请检查响应报文是否是JSON")
                    return
                }
                // 服务端响应是否成功
                if !self.isServerValid(dict: dict) {
                    self.show(text: self.errorInfo(dict: dict))
                    return
                }
                // 返回到主线程
                DispatchQueue.main.async {
                    callback(dict)
                }
            })
            task.resume()
        }
    }
    
    // 状态码和描述信息
    private func errorInfo(dict:NSDictionary) -> String {
        guard let statusCode = dict.value(forKey: "statusCode") else {
            return "失败"
        }
        guard let description = dict.value(forKey: "description") else {
            return "失败"
        }
        return "错误码：\(statusCode) 错误描述：\(description)"
    }
    
    // 服务端响应是否成功
    private func isServerValid(dict:NSDictionary) -> Bool {
        let status = isServerSuccess(dict: dict)
        // 未开通放回成功
        if status == 1205 {
            return true
        }
        return 1200 == status
    }
    
    // 是否是1200，成功
    func isServerSuccess(dict:NSDictionary) -> NSInteger {
        guard let statusCode = dict.value(forKey: "statusCode") else {
            return 0
        }
        return (statusCode as! NSInteger)
    }
    
    // 拼接请求报文
    func regStatusRequest(status:Int,desc:String) -> NSDictionary {
        let dict = NSMutableDictionary()
        dict.setValue(desc, forKey: "desc")
        dict.setValue(status, forKey: "status")
        dict.setValue(UIDevice.current.identifierForVendor?.uuidString, forKey: "deviceid")
        dict.setValue(UserDefaults.standard.value(forKey: SP_USERNAME) as? String, forKey: SP_USERNAME)
        return dict
    }
    
    // 两个日期相差多少天
    func dateInterval(start:String?,end:String?) -> Bool {
        let formatter = DateFormatter()
        formatter.dateFormat = "yyyy-MM-dd"
        guard let endStr = end, let endDate = formatter.date(from: endStr) else {
            return true
        }
        guard let startStr = start, let startDate = formatter.date(from: startStr) else {
            return true
        }
        let day = NSCalendar.current.dateComponents([.day], from: startDate, to: endDate).day
        return day! < 0
    }
    
    // 保存用户信息到偏好
    func saveUserInfo(userInfo:UserInfo) -> Void {
        UserDefaults.standard.setValue(userInfo.mobile, forKey: SP_MOBILE)
        UserDefaults.standard.setValue(userInfo.userid, forKey: SP_USERID)
        UserDefaults.standard.setValue(userInfo.password, forKey: SP_PASSWORD)
        UserDefaults.standard.setValue(userInfo.idnumber, forKey: SP_IDNUMBER)
        UserDefaults.standard.setValue(userInfo.username, forKey: SP_USERNAME)
        UserDefaults.standard.setValue(userInfo.updatetime, forKey: SP_UPDATETIME)
        UserDefaults.standard.setValue(userInfo.permissionid, forKey: SP_PERMISSIONID)
        // 校验用户会员是否过期
        if userInfo.expiredate != nil ,self.dateInterval(start: userInfo.serveredate, end: userInfo.expiredate) {
            UserDefaults.standard.setValue(3, forKey: SP_PERMISSIONID)
            // 会员过期 修改数据库
            self.modifyMemberExpire()
        }
    }
    
    // 会员过期
    func modifyMemberExpire() -> Void {
        // 解析数据
        guard let userid = UserDefaults.standard.value(forKey: SP_USERID) else {
            return
        }
        // 拼接数据
        let request = NSMutableDictionary()
        request.setValue(userid, forKey: SP_USERID)
        // 请求
        self.doPost(api: "modify/user", dict: request) { (dict) in
            
        }
    }
    
    // 显示提示框
    func showDialog(str:String) -> Void {
        let alert = UIAlertController(title: "提示", message: "\n\(str)", preferredStyle: .alert)
        alert.addAction(UIAlertAction(title: "确定", style: .default, handler: nil))
        present(alert, animated: true, completion: nil)
    }
}
